package algorithms

import (
	"context"
	"fmt"
	"math"
	"runtime"
	"sync"
	"time"
)

// ComputeOptimizer 计算密集型任务优化器
type ComputeOptimizer struct {
	workerCount int
	cacheSize   int
	resultCache *LRUCache
	mu          sync.RWMutex
}

// NewComputeOptimizer 创建计算优化器
func NewComputeOptimizer() *ComputeOptimizer {
	return &ComputeOptimizer{
		workerCount: runtime.NumCPU(),
		cacheSize:   1000,
		resultCache: NewLRUCache(1000),
	}
}

// ParallelCompute 并行计算任务
func (co *ComputeOptimizer) ParallelCompute(tasks []func() interface{}) []interface{} {
	if len(tasks) == 0 {
		return nil
	}

	results := make([]interface{}, len(tasks))
	var wg sync.WaitGroup
	semaphore := make(chan struct{}, co.workerCount)

	for i, task := range tasks {
		wg.Add(1)
		go func(index int, fn func() interface{}) {
			defer wg.Done()
			semaphore <- struct{}{} // 获取信号量
			defer func() { <-semaphore }() // 释放信号量

			results[index] = fn()
		}(i, task)
	}

	wg.Wait()
	return results
}

// OptimizedLoop 优化循环结构
func (co *ComputeOptimizer) OptimizedLoop(data []interface{}, processor func(interface{}) interface{}) []interface{} {
	if len(data) == 0 {
		return nil
	}

	// 小数据集直接处理
	if len(data) < 100 {
		results := make([]interface{}, len(data))
		for i, item := range data {
			results[i] = processor(item)
		}
		return results
	}

	// 大数据集并行处理
	chunkSize := len(data) / co.workerCount
	if chunkSize == 0 {
		chunkSize = 1
	}

	results := make([]interface{}, len(data))
	var wg sync.WaitGroup

	for i := 0; i < len(data); i += chunkSize {
		end := i + chunkSize
		if end > len(data) {
			end = len(data)
		}

		wg.Add(1)
		go func(start, end int) {
			defer wg.Done()
			for j := start; j < end; j++ {
				results[j] = processor(data[j])
			}
		}(i, end)
	}

	wg.Wait()
	return results
}

// CachedCompute 带缓存的计算
func (co *ComputeOptimizer) CachedCompute(key string, computeFn func() interface{}) interface{} {
	// 检查缓存
	if result, found := co.resultCache.Get(key); found {
		return result
	}

	// 计算结果
	result := computeFn()

	// 缓存结果
	co.resultCache.Put(key, result, 10*time.Minute)
	return result
}

// RecursionOptimizer 递归优化器
type RecursionOptimizer struct {
	memoCache *LRUCache
	maxDepth  int
}

// NewRecursionOptimizer 创建递归优化器
func NewRecursionOptimizer(maxDepth int) *RecursionOptimizer {
	return &RecursionOptimizer{
		memoCache: NewLRUCache(1000),
		maxDepth:  maxDepth,
	}
}

// OptimizedRecursion 优化递归调用
func (ro *RecursionOptimizer) OptimizedRecursion(key string, depth int, recursiveFn func() interface{}) interface{} {
	// 检查深度限制
	if depth > ro.maxDepth {
		return nil
	}

	// 检查备忘录缓存
	if result, found := ro.memoCache.Get(key); found {
		return result
	}

	// 执行递归计算
	result := recursiveFn()

	// 缓存结果
	ro.memoCache.Put(key, result, 30*time.Minute)
	return result
}

// MathOptimizer 数学计算优化器
type MathOptimizer struct {
	lookupTable map[string]float64
	mu          sync.RWMutex
}

// NewMathOptimizer 创建数学优化器
func NewMathOptimizer() *MathOptimizer {
	mo := &MathOptimizer{
		lookupTable: make(map[string]float64),
	}
	
	// 预计算常用数学函数值
	mo.precomputeCommonValues()
	return mo
}

// precomputeCommonValues 预计算常用值
func (mo *MathOptimizer) precomputeCommonValues() {
	// 预计算sin, cos, tan等常用角度
	commonAngles := []float64{0, math.Pi/6, math.Pi/4, math.Pi/3, math.Pi/2, math.Pi}
	for _, angle := range commonAngles {
		mo.lookupTable["sin_"+floatToString(angle)] = math.Sin(angle)
		mo.lookupTable["cos_"+floatToString(angle)] = math.Cos(angle)
		mo.lookupTable["tan_"+floatToString(angle)] = math.Tan(angle)
	}

	// 预计算常用对数值
	for i := 1; i <= 100; i++ {
		val := float64(i)
		mo.lookupTable["log_"+floatToString(val)] = math.Log(val)
		mo.lookupTable["log10_"+floatToString(val)] = math.Log10(val)
	}
}

// FastSin 快速sin计算
func (mo *MathOptimizer) FastSin(x float64) float64 {
	key := "sin_" + floatToString(x)
	mo.mu.RLock()
	if val, exists := mo.lookupTable[key]; exists {
		mo.mu.RUnlock()
		return val
	}
	mo.mu.RUnlock()

	// 计算并缓存
	result := math.Sin(x)
	mo.mu.Lock()
	mo.lookupTable[key] = result
	mo.mu.Unlock()
	return result
}

// FastCos 快速cos计算
func (mo *MathOptimizer) FastCos(x float64) float64 {
	key := "cos_" + floatToString(x)
	mo.mu.RLock()
	if val, exists := mo.lookupTable[key]; exists {
		mo.mu.RUnlock()
		return val
	}
	mo.mu.RUnlock()

	result := math.Cos(x)
	mo.mu.Lock()
	mo.lookupTable[key] = result
	mo.mu.Unlock()
	return result
}

// PerformanceMonitor 性能监控器
type PerformanceMonitor struct {
	metrics map[string]*PerformanceMetric
	mu      sync.RWMutex
}

// PerformanceMetric 性能指标
type PerformanceMetric struct {
	TotalCalls   int64
	TotalTime    time.Duration
	AverageTime  time.Duration
	MinTime      time.Duration
	MaxTime      time.Duration
	LastCallTime time.Time
}

// NewPerformanceMonitor 创建性能监控器
func NewPerformanceMonitor() *PerformanceMonitor {
	return &PerformanceMonitor{
		metrics: make(map[string]*PerformanceMetric),
	}
}

// MeasureExecution 测量执行时间
func (pm *PerformanceMonitor) MeasureExecution(name string, fn func()) {
	start := time.Now()
	fn()
	duration := time.Since(start)

	pm.mu.Lock()
	defer pm.mu.Unlock()

	metric, exists := pm.metrics[name]
	if !exists {
		metric = &PerformanceMetric{
			MinTime: duration,
			MaxTime: duration,
		}
		pm.metrics[name] = metric
	}

	metric.TotalCalls++
	metric.TotalTime += duration
	metric.AverageTime = time.Duration(int64(metric.TotalTime) / metric.TotalCalls)
	metric.LastCallTime = time.Now()

	if duration < metric.MinTime {
		metric.MinTime = duration
	}
	if duration > metric.MaxTime {
		metric.MaxTime = duration
	}
}

// GetMetrics 获取性能指标
func (pm *PerformanceMonitor) GetMetrics(name string) *PerformanceMetric {
	pm.mu.RLock()
	defer pm.mu.RUnlock()
	return pm.metrics[name]
}

// TaskScheduler 任务调度器
type TaskScheduler struct {
	workerPool *WorkerPool
	taskQueue  chan Task
	ctx        context.Context
	cancel     context.CancelFunc
}

// Task 任务定义
type Task struct {
	ID       string
	Priority int
	Execute  func() interface{}
	Callback func(interface{})
}

// TaskJob 实现Job接口的任务包装器
type TaskJob struct {
	task Task
}

// Execute 实现Job接口
func (tj *TaskJob) Execute() (interface{}, error) {
	result := tj.task.Execute()
	if tj.task.Callback != nil {
		tj.task.Callback(result)
	}
	return result, nil
}

// ID 实现Job接口
func (tj *TaskJob) ID() string {
	return fmt.Sprintf("task-%d", time.Now().UnixNano())
}

// NewTaskScheduler 创建任务调度器
func NewTaskScheduler(workerCount int) *TaskScheduler {
	ctx, cancel := context.WithCancel(context.Background())
	return &TaskScheduler{
		workerPool: NewWorkerPool(workerCount, 1000),
		taskQueue:  make(chan Task, 1000),
		ctx:        ctx,
		cancel:     cancel,
	}
}

// Start 启动调度器
func (ts *TaskScheduler) Start() {
	ts.workerPool.Start()
	go ts.processQueue()
}

// Stop 停止调度器
func (ts *TaskScheduler) Stop() {
	ts.cancel()
	ts.workerPool.Stop()
	close(ts.taskQueue)
}

// ScheduleTask 调度任务
func (ts *TaskScheduler) ScheduleTask(task Task) {
	select {
	case ts.taskQueue <- task:
	case <-ts.ctx.Done():
	}
}

// processQueue 处理任务队列
func (ts *TaskScheduler) processQueue() {
	for {
		select {
		case task := <-ts.taskQueue:
			// 创建一个实现Job接口的任务
	job := &TaskJob{
		task: task,
	}
	ts.workerPool.Submit(job)
		case <-ts.ctx.Done():
			return
		}
	}
}

// 辅助函数
func floatToString(f float64) string {
	return fmt.Sprintf("%.6f", f)
}